package gameState;

import java.io.Serializable;
import java.util.ArrayList;

import scala40rules.Card;
import scala40rules.CardSet;
import scala40rules.CardSetList;


public class Baloon implements Serializable{
	
	/**
	 * 
	 */
	private static final long serialVersionUID = 1L;
	private	CardSetList baloon = new CardSetList();
	private static final int minScoreForOpen = 40;
	private static final int maxScorePossible = 140;
	
	//----------------------------- COSTRUTTORI -----------------------------------//
	
	public Baloon(CardSetList baloon) {
		this.baloon = baloon;
	}

	public Baloon(){
		
	}
	
	//----------------------------- GET and SET basilari -----------------------------------//
	
	public void setBaloon(CardSetList baloon) {
		this.baloon = baloon;
	}

	public CardSetList getBaloon() {
		return baloon;
	}
	
	public CardSet getBaloonLevel(int baloonLevel){
		return this.baloon.getCardSet(baloonLevel);
	}
	
	public void setBaloonLevel(int baloonLevel, CardSet cs){
		this.baloon.setCardSetList(baloonLevel, cs);
	}
	
	public CardSetList getAllValidBaloonLevel(){
		CardSetList csl = new CardSetList();
		for(int i=0; i<this.baloon.size(); i++){
			if(this.baloon.getCardSet(i).isValidSet()){
				csl.addCardSet(this.baloon.getCardSet(i));
			}
		}
		return csl;
	}
	
	//----------------------------- Metodi per la gestione -----------------------------------//
	
	public int size(){
		return this.baloon.size();
	}
	
	public int getLastLevel(){
		if(this.size()==0){
			return 0;
		}
		else{
			return this.size()-1;
		}
	}
	
	public void addCardSet(CardSet cardSet){
		this.baloon.addCardSet(cardSet);
	}
	
	public CardSet removeCardSet(int baloonLevel){
		if(this.getBaloon().size()>baloonLevel){
			CardSet cs = this.baloon.removeCardSetFromList(baloonLevel);
			return cs;
		}else{
			return new CardSet();
		}
	}
	
	public CardSetList removeAllCardSet(){
		return this.baloon.removeAllCardSet();
	}
	
	public CardSetList removeAllValidCardSet(){
		if(this.baloon.getCardSet(this.baloon.size()-1).isValidSet()){
			System.out.println("[Baloon || removeAllValidCardSet()] sono tutti validi");
			CardSetList csl = this.baloon.removeAllCardSet();
			return csl;
		}else{
			if(this.baloon.getCardSet(this.baloon.size()-1).size()!=0){
				System.out.println("[Baloon || removeAllValidCardSet()] l'ultimo non e' valido");
				CardSet cardSet = this.baloon.removeCardSetFromList(this.baloon.size()-1);
				CardSetList csl = this.baloon.removeAllCardSet();
				this.baloon.addCardSet(cardSet);
				return csl;
			}
			
			System.out.println("[Baloon || removeAllValidCardSet()] l'ultimo non e' valido perche' e' vuoto");
			CardSetList csl = this.baloon.removeAllCardSet();
			return csl;
		}
	}
	
	
	public void resetJokerAtLevel(int baloonLevel){
		this.baloon.getCardSet(baloonLevel).resetJoker();
	}
	
	public boolean newBaloonLevel(){
		System.out.println("[Baloon || newBaloonLevel()] baloon.size="+this.baloon.size());
		if( ( this.baloon.size() > 0 ) && ( this.baloon.getCardSet(this.baloon.size()-1).isValidSet() ) ){
			this.baloon.addCardSet(new CardSet());
			return true;
		}
		else{
			System.out.println("-[Error]- [Baloon || newBaloonLevel()] impossibile aggiungere una nuova riga, l'ultima riga inserita non e' valida");
			return false;
		}
	}
	
	public boolean addCardToLastBaloonLevel(Card card){
		if (this.baloon.size()==0){
			CardSet cs= new CardSet();
			cs.addCard(card);
			this.baloon.addCardSet(cs);
			return true;
			
		}
		else{
			int baloonLevel= this.baloon.size()-1;
			if(this.baloon.getCardSet(baloonLevel).size() < 6){
				this.baloon.getCardSet(baloonLevel).addCard(card);
				return true;
			}
		}
		System.out.println("-[Error]- [Ballon || addCardToLastBaloonLevel()] impossibile aggiungere carta all'ultima linea ");
		return false;
	}
	
	public boolean addCardToBaloonLevel(int baloonLevel, Card card){
		if( (this.baloon.size() > baloonLevel) && (this.baloon.getCardSet(baloonLevel).size() < 6) ){
			this.baloon.getCardSet(baloonLevel).addCard(card);
			return true;
		}else{
			System.out.println("-[Error]- [Ballon || addCardToBaloonLevel()] impossibile aggiungere carta alla linea "+ baloonLevel+1);
			return false;
		}
	}

	//----------------------------- Metodi necessari per il gioco -----------------------------------//
	
	//possoScalare?:boolean
	public boolean canOpen(){
		int totalSum=0;
		int value=0;
		for(int i=0; i<this.size();i++){
			if(this.getBaloonLevel(i).size()!=0){
				value = this.getBaloonLevel(i).sumValidCardsetValue();
				System.out.println("[Baloon || canOpen()] aggiungo a totalSum "+value);
				totalSum += value;
			}
		}
		System.out.println("[Baloon || canOpen()]"+((totalSum >= minScoreForOpen) && (totalSum<maxScorePossible))
				+" totalSum="+totalSum);
		return ((totalSum >= minScoreForOpen) && (totalSum<maxScorePossible));

	}
	
	
	

	//TODO metti giu' uno o piu' cardSet
	
	


	
	
	
	
	// -------------------------------- METODI PER IL TESTING ------------------------ //
	
	public void stampaAllBaloon(){
		System.out.println(" Carte nel Baloon :");
		for(int i=0; i<this.baloon.size(); i++){
			System.out.println(" CardSet n."+i+": ");
			for(int j=0; j<this.baloon.getCardSet(i).size();j++){
				System.out.println("      "+this.baloon.getCardSet(i).getCard(j).getSymbol()+" "+this.baloon.getCardSet(i).getCard(j).getSuit());
			}
		}
	}
	
}
